#pragma once

#include "../umlmodel_global.h"

#include <memory>
#include <vector>

#include "MultiplicityElement.h"

using std::make_shared;
using std::shared_ptr;
using std::vector;

namespace uml {
class ConnectableElement;
class Property;

/// <summary>
/// ConnectorEnd
/// A ConnectorEnd is an endpoint of a Connector, which attaches the Connector to a
/// ConnectableElement.
/// </summary>
class UMLMODEL_EXPORT ConnectorEnd : public MultiplicityElement {

public: // JsonSerializable override
    void fromJson(const QJsonObject& json, QStringList& errorList) override;
    void toJson(QJsonObject& json) override;

public: // Methods
public: // Properties
    /// <summary>
    /// definingEnd getter
    /// A derived property referencing the corresponding end on the Association which
    /// types the Connector owing this ConnectorEnd, if any. It is derived by selecting
    /// the end at the same place in the ordering of Association ends as this
    /// ConnectorEnd.
    /// </summary>
    shared_ptr<Property> definingEnd() const;

    /// <summary>
    /// definingEnd setter
    /// A derived property referencing the corresponding end on the Association which
    /// types the Connector owing this ConnectorEnd, if any. It is derived by selecting
    /// the end at the same place in the ordering of Association ends as this
    /// ConnectorEnd.
    /// </summary>
    void setDefiningEnd(shared_ptr<Property> value);

    /// <summary>
    /// partWithPort getter
    /// Indicates the role of the internal structure of a Classifier with the Port to
    /// which the ConnectorEnd is attached.
    /// </summary>
    shared_ptr<Property> partWithPort() const;

    /// <summary>
    /// partWithPort setter
    /// Indicates the role of the internal structure of a Classifier with the Port to
    /// which the ConnectorEnd is attached.
    /// </summary>
    void setPartWithPort(shared_ptr<Property> value);

    /// <summary>
    /// role getter
    /// The ConnectableElement attached at this ConnectorEnd. When an instance of the
    /// containing Classifier is created, a link may (depending on the multiplicities)
    /// be created to an instance of the Classifier that types this ConnectableElement.
    /// </summary>
    shared_ptr<ConnectableElement> role() const;

    /// <summary>
    /// role setter
    /// The ConnectableElement attached at this ConnectorEnd. When an instance of the
    /// containing Classifier is created, a link may (depending on the multiplicities)
    /// be created to an instance of the Classifier that types this ConnectableElement.
    /// </summary>
    void setRole(shared_ptr<ConnectableElement> value);

private: // Fields
    /// <summary>
    /// definingEnd
    /// A derived property referencing the corresponding end on the Association which
    /// types the Connector owing this ConnectorEnd, if any. It is derived by selecting
    /// the end at the same place in the ordering of Association ends as this
    /// ConnectorEnd.
    /// </summary>
    shared_ptr<Property> definingEnd_;

    /// <summary>
    /// partWithPort
    /// Indicates the role of the internal structure of a Classifier with the Port to
    /// which the ConnectorEnd is attached.
    /// </summary>
    shared_ptr<Property> partWithPort_;

    /// <summary>
    /// role
    /// The ConnectableElement attached at this ConnectorEnd. When an instance of the
    /// containing Classifier is created, a link may (depending on the multiplicities)
    /// be created to an instance of the Classifier that types this ConnectableElement.
    /// </summary>
    shared_ptr<ConnectableElement> role_;

};

} // namespace uml
